package eu.jakubiak.mcc.protocol;

import java.io.UnsupportedEncodingException;
import java.net.URLEncoder;
import java.util.regex.Matcher;
import java.util.regex.Pattern;

import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

import eu.jakubiak.mcc.enums.Status;

/**
 * Implementacja protokołu Multimedia Conversion
 * 
 * @author Antek
 */

public class Protocol {
    /**
     * Logger
     */
    private static final Logger logger = LoggerFactory.getLogger(Protocol.class);

    /**
     * Adres rootUrl dla serwera MC
     */
    private String rootUrl;
    public String getRootUrl() {
        return rootUrl;
    }
    public void setRootUrl(String rootUrl) {
        this.rootUrl = rootUrl;
    }

    /**
     * Url encoding 
     * 
     * @param url
     * @return
     */
    protected String urlEncode(String string) {
        try {
            return URLEncoder.encode(string, "US-ASCII");
        } catch(UnsupportedEncodingException e) {
            logger.error("Unsuported encoding US-ASCII");
            return string;
        }
    }
    
    
    /**
     * Create URL address for initialize the conversion
     * 
     * @param fileUrl   URL address of source file, could be Westly formatted
     * @param format    output format, supported are FLV, H264,
     * @param quality   conversion quality or NULL,
     * @param statusUrl URL address for getting response from Multimedia Conversion Server
     * 
     * @return URL address
     */
    public String createUrlForBeginConversion(String fileUrl, String format, String quality, String statusUrl) {
        StringBuilder sb = new StringBuilder();
        sb.append(rootUrl);
        sb.append("?method=upload");
        sb.append("&url=");
        sb.append(urlEncode(fileUrl));
        sb.append("&format=");
        sb.append(urlEncode(format));
        if (quality!=null) {
            sb.append("&quality=");
            sb.append(urlEncode(quality));
        }
        if(statusUrl!=null) {
            sb.append("&statusUrl=");
            sb.append(urlEncode(statusUrl));
        }
        return sb.toString();
    }
 
    /**
     * Create URL for status query
     * 
     * @param key unique key of conversion
     * @return URL address
     */
    public String createUrlForStatus(String key) {
        StringBuilder sb = new StringBuilder();
        sb.append(rootUrl);
        sb.append("?method=check");
        sb.append("&jobId=");
        sb.append(urlEncode(key));
        return sb.toString();
    }
    
    /**
     * Create URL for getting thumb jpeg image
     * 
     * @param key unique key of conversion
     * @return URL address
     */
    public String createUrlForThumb(String key) {
        StringBuilder sb = new StringBuilder();
        sb.append(rootUrl);
        sb.append("?method=thumb");
        sb.append("&jobId=");
        sb.append(urlEncode(key));
        return sb.toString();
    }
    
    /**
     * Create URL for getting result video
     * 
     * @param key unique key of conversion process
     * @return URL address
     */
    public String createUrlForResult(String key) {
        StringBuilder sb = new StringBuilder();
        sb.append(rootUrl);
        sb.append("?method=get");
        sb.append("&jobId=");
        sb.append(urlEncode(key));
        return sb.toString();
    }
    
    
    
    /**
     * parsing response for start command and getting unique key for
     * conversion 
     * 
     * @param beginResponse string containt response from begin query on multimedia conversion server
     * @return unique key or null
     */
    public String parseBeginResponseAndGetKey(String beginResponse) {
        Matcher matcher = BEGIN_RESPONSE_PARSER.matcher(beginResponse);
        if(matcher.find()) {
            return matcher.group(1);
        }
        return null;
    }
    
    /**
     * The simplies way to parse response from multimedia conversion server
     */
    private final Pattern BEGIN_RESPONSE_PARSER = Pattern.compile("<jobId>([a-zA-Z0-9]+)</jobId>");
    
    
    /**
     * parsing response for status command and getting current status of conversion
     * conversion 
     * 
     * @param beginResponse string containt response from begin query on multimedia conversion server
     * @return unique key or null
     */
    public Status parseStatusResponseAndGetStatus(String statusResponse) {
        Matcher matcher = STATUS_RESPONSE_PARSER.matcher(statusResponse);
        if(matcher.find()) {
            String statusString = matcher.group(1);
            return Status.find(statusString);
        }
        return null;
    }
    
    /**
     * The simplies way to parse status response from multimedia conversion server
     */
    private final Pattern STATUS_RESPONSE_PARSER = Pattern.compile("<state>([a-zA-Z0-9]+)</state>");
}
